using System.Reflection;
using System.Text;
using Iuliia;
using IuliiaBot.Application.Interfaces;

namespace IuliiaBot.Application.Commands
{
    public class TransliteCommand : CommandBase, IUseMessageCommand
    {
        public string Message { get; private set; } = default!;

        public void SetMessage(string message)
        {
            Message = message;
        }

        protected override async Task<bool> InternalCommand()
        {
            Dictionary<string, List<string>> translations = new();
            var fields = typeof(Schemas).GetRuntimeFields();    // Получение совойств статического класса Iuliia.Schemas

            foreach (var field in fields)
            {
                var scheme = field.GetValue(null) as Scheme;
                if (scheme == null)
                {
                    throw new InvalidCastException("Scheme is null");
                }
                var transText = IuliiaTranslator.Translate(Message, scheme);

                if (translations.ContainsKey(transText))
                {
                    translations[transText].Add(scheme.Name);
                }
                else 
                {
                    translations.Add(transText, new List<string>() { scheme.Name });
                }
            }

            StringBuilder sb = new StringBuilder();

            foreach (var translation in translations) 
            {
                sb.Append("<b>");
                var schemes = translation.Value;
                for (int i = 0; i < schemes.Count; i++)
                {
                    sb.Append(schemes[i]);
                    if (i != schemes.Count - 1) sb.Append(", ");
                }
                sb.Append(":</b>\n");
                sb.Append("<code>");
                sb.Append(translation.Key);
                sb.Append("</code>\n");
            }

            const int maxMessageLength = 4000;
            for (int charactersSent = 0; charactersSent < sb.Length - 1; )
            {
                var msgSeparationPattern = "<b>";
                bool including = false;
                int length;
                if (charactersSent + maxMessageLength < sb.Length) length = maxMessageLength;
                else length = sb.Length - charactersSent;

                string searchString = sb.ToString(charactersSent, length);
                var i = searchString.LastIndexOf(msgSeparationPattern);

                string text;
                if (i <= 0)
                {
                    text = searchString;
                }
                else
                {
                    text = sb.ToString(charactersSent, i + (including ? msgSeparationPattern.Length : 0));
                }
                
                charactersSent += text.Length;

                await _sander.SandMessage(text);
            }

            return true;
        }


        public TransliteCommand(ISander sander) : base(sander) { }
    }
}